package com.elhakimz.matra.actor;

import com.elhakimz.matra.pattern.ISignalSlot;
import com.elhakimz.matra.pattern.SignalType;
import com.elhakimz.matra.geo.GeoPoint;
import com.elhakimz.matra.util.GlobalVars;
import com.elhakimz.matra.battle.BattleManager;
import com.jme.math.Vector3f;

import java.util.HashMap;
import java.util.Map;


/**
 * Simulation Actor Class 
 */
public class Actor implements ISignalSlot {

    private ActorData actorData;
    private ActorGL actorGL;
    private ActorAI actorAI;


    private String name;
    private String faction;
    private HashMap valueHolder;
    private String platformType;


    //constructor
    public Actor(String name, String faction, String model) {
        this.name= name;
        this.actorData = new ActorData(name+"-ds");
        this.actorGL = new ActorGL(name+"-gl",model);
        this.actorAI = new ActorAI(name+"-clc");
        this.faction=faction;
        this.valueHolder=new HashMap();
        this.platformType = "NAVAL";
    }

    //signal
    public void signal(SignalType signal) {


        SignalType oksig = new SignalType(SignalType.SIG_TYPE_RESPONSE,
                SignalType.SIG_SIGN_OK,this,null );

        if(signal.type.equals(SignalType.SIG_TYPE_COMMAND)){

          // get command from USER of this object
          //do something, if its okay response OK,
          // otherwise response NOK

          signal.sender.signal(oksig);  //send OK message


        }else if(signal.type.equals(SignalType.SIG_TYPE_RESPONSE)){

          // get response from INSIDE object
          //think something after the answer,
          // it would be just  data sent,
            if((signal.sender instanceof ActorData) && (signal.sign.equals("POS"))){
               setValueHolder(signal.sign, signal.parameters); //just keep this value for later use
            }
            else if((signal.sender instanceof ActorData) && (signal.sign.equals("SNS"))){
              //sensor data received
            }
            else if((signal.sender instanceof ActorData) && (signal.sign.equals("TRK"))){
             //track data received
            }
        }
    }

    private void setValueHolder(String sign, Map params){
        if(sign.equals("POS")){
          valueHolder.put("POS-LAT",params.get("LAT"));
          valueHolder.put("POS-LON",params.get("LON"));
          valueHolder.put("POS-ALT",params.get("ALT"));
          valueHolder.put("POS-HDG",params.get("HDG"));
          valueHolder.put("POS-SPD",params.get("SPD"));
          valueHolder.put("POS-TIME",params.get("TIME")); //server time
        }
    }

    public String getName() {
        return name;
    }

    public Actor activate(){
       actorGL.attach();
       GlobalVars.battleManager.signal(new SignalType(SignalType.SIG_TYPE_RESPONSE,
               BattleManager.ACTOR_ACTIVE,this,null));
        return this;
    }

    //placement
    public Actor setPos(float lat, float lon, float alt){
       actorGL.setPos(lat,lon,alt);
       return this;
    }


    //SETTINGS

    public Actor setSpeed(float n){
        valueHolder.put("SPEEDSET",n);
        // TODO if ActorGL is running the animation progress, set speed to it
        actorGL.setSpeed(n);
        return this;
        
    }

    public void setAltitude(float alt){
        valueHolder.put("ALTSET",alt);
    }

    public void setPoint(float lat, float lon){
        GeoPoint gpt = new GeoPoint(lat,lon,0);
        valueHolder.put("POINTSET",gpt);
    }

    public void setTarget(Actor act){
        valueHolder.put("TGTSET",act);
    }

    //highlighting

    public void highlight(){
      // TODO highlight unit, display billboard
    }


 //--movements--

    public void move(){
       //TODO avoid current movement then direct movement vector to point

    }

    public void stop(){
        //TODO stop current movement
    }

    public void followTrack(){
       //TODO follow a Track object whether enemy or friend
    }


    public Actor followWaypoints(Vector3f[] points){
      //TODO avoid current movement then follow a Waypoint path
       actorGL.followWaypoints(points);
       return this;

    }

    public void returnToBase(){
     //TODO RTB

    }

    public void land(){
       //TODO landing

    }


//-- patrolling
    public void patrolPoint(float lat, float lon){
      //todo move to a point then do patrol zigzag or encircling
      //in 50km radius from the point

    }

    public void patrolArea(float lat1, float lon1, float lat2, float lon2){
     //todo patrol an area defined by the float
    }

//hostility movement
   public void intercept(){
    //todo intercept a selected track

   }

   public void engage(){
    //todo engage a selected track

   }

   public void attack(){
     //todo attack a selected track

   }

   public void pursue(){
    //todo pursue a selected track

   }

   public void flee(){
    //todo flee from a selected track

   }


//--sensors

    public void activateSensor(int index){
    //todo activate sensor

    }

    public void activateAllSensor(){
    //todo activate all sensor

    }

    public void inactiveSensor(int index){
    //todo inactivate sensor


    }

    public void trackTarget(){
    //todo okay track the enemy

    }

    public void aimTarget(){
    //todo prepare a hot weapon   

    }

//weaponry
    public void launch(){
     //todo launch a hot weapon
    }

    public void shoot(){
     //todo shoot using guns

    }
    
    public void dropChaff(){
     //todo drop chaff


    }

    public void dropFlare(){
     //todo drop flare   

    }

}
